package schoolsource.model;

import java.util.logging.Level;

import schoolsource.sql.DBSQLAccessor;
import schoolsource.util.SchoolLogger;

/**
*
* The Item class is used to represent all field data within the DB and within the jsp.
*
**/
public abstract class Item {

	// Used for both the DB column name and the jsp field name
	private String fieldName = null;
	// The error describing why the item is not valid
	private String errorString = null;
	// Indicates whether or not the item is valid
	//   validate must be run first for this to be accurate.
	protected boolean valid = true;
	// Indicates whether the field must have a value
	private boolean required = false;

	/**
	*
	* setValue must set the item's true value from a string. The true value may
	* be a String, int, double, char, etc.
	*
	**/
	abstract public void setValue(String newValue);

	/**
	*
	* setTrueValue must set the item's true value from the type of object that the true value
	* is. If the true value is a simple type, use the object form (Integer for int, etc).
	*
	**/
	abstract public void setTrueValue(Object newTrueValue);

	/**
	*
	* toString returns the String representation of the true value.
	*
	**/
	abstract public String toString();

	/**
	*
	* getObject returns the object representation of the true value. If the true value is
	* a simple type, use the object form (Integer for in, etc).
	*
	**/
	abstract public Object getObject();

	/**
	*
	* getDBFormattedString uses the getDBFormatted*** in the DBSQLAccessor object
	* to return the appropriate representation of the true value for the particular
	* DB that is used.(Each DBSQLAccessor is written specificly for a DB.)
	*
	**/
	abstract public String getDBFormattedString(DBSQLAccessor dba);

	/**
	*
	* createFromDBString uses the removeDBTagsFrom*** in the DBSQLAccessor object
	* to parse and set the true value from the results of a DB query
	* (Each DBSQLAccessor is written specificly for a DB.)
	*
	**/
	abstract public void createFromDBString(String dbString, DBSQLAccessor dba);

	/**
	*
	* validate parses the true value of the item and determines whether it is valid due to basic
	* business rules. More advanced business rules must be validated externally. If the
	* value is not valid, the error string should be set with the reason it is not valid.
	*
	**/
	abstract public void validate();

	/**
	*
	* isValid returns the state of the valid variable. Note: validate() must be run prior
	* to isValid to get a true result. This is done because isValid is meant to reflect both
	* whether the single value is valid and whether it complies with business rules involving
	* other values (e.g. a start date and end date where the start date is after the end date).
	*
	**/
	abstract public boolean isValid();

	/**
	*
	* setFieldName takes in the String representing the field the item represents.
	* fieldName is used for both the DB and the jsp page.
	*
	**/
	public void setFieldName(String newFieldName) {
		if (newFieldName != null && !newFieldName.equals("")) {
			fieldName = newFieldName;
		}
	}

	/**
	*
	* getFieldName returns the String representing the field the item represents.
	* fieldName is used for both the DB and the jsp page.
	*
	**/
	public String getFieldName() {
		return fieldName;
	}

	/**
	*
	* setErrorString takes in a string representing the reason the item is not valid.
	*
	**/
	public void setErrorString(String newErrorString) {
		errorString = newErrorString;
	}

	/**
	*
	* getErrorString returns a String describing the reason the item is not valid.
	*
	**/
	public String getErrorString() {
		return errorString;
	}

	/**
	*
	* setRequired takes in a boolean used to indicate whether or not the item must have
	* a value in order to be valid.
	*
	**/
	public void setRequired(boolean newVal) {
		required = newVal;
	}

	/**
	*
	* isRequired returns a boolean representing whether the field must have a value in order
	* to be valid
	*
	**/
	public boolean isRequired() {
		return required;
	}

	/**
	*
	* setValid takes in a boolean used to indicate whether or not the item is valid.
	* This is used for more advanced business rule checking.
	*
	**/
	public void setValid(boolean newVal) {
		valid = newVal;
		if (newVal) {
			setErrorString(null);
		}
	}

	/**
	*
	* printValues is used to output all values contained within the item to the log.
	*
	**/
	public void printValues() {
		if (getFieldName() != null) {
			SchoolLogger.logger.log(
				Level.INFO,
				"Item.getFieldName(): " + getFieldName());
		} else {
			SchoolLogger.logger.log(Level.INFO, "Item.getFieldName() == null");
		}
		if (getFieldName() != null) {
			SchoolLogger.logger.log(
				Level.INFO,
				"Item.toString(): " + toString());
		} else {
			SchoolLogger.logger.log(Level.INFO, "Item.toString() == null");
		}
		if (getFieldName() != null) {
			SchoolLogger.logger.log(
				Level.INFO,
				"Item.getErrorString(): " + getErrorString());
		} else {
			SchoolLogger.logger.log(
				Level.INFO,
				"Item.getErrorString() == null");
		}
		if (getFieldName() != null) {
			//new RuntimeException().printStackTrace(Log.out);
			SchoolLogger.logger.log(
				Level.INFO,
				"Item.isRequired(): " + isRequired(),
				new RuntimeException());
		} else {
			SchoolLogger.logger.log(Level.INFO, "Item.isRequired() == null");
		}
	}
}
